import ij.ImagePlus;
import ij.plugin.PlugIn;
import ij.process.ColorProcessor;
import ij.process.ImageProcessor;


import java.awt.Color;


import java.awt.Font;

import java.awt.Polygon;
import java.io.PrintStream;

import java.util.ArrayList;
import java.util.Locale;
import java.util.Random; 

import pluginUtils.Matrix4D;
import pluginUtils.Point2D;
import pluginUtils.Polytope;

import pluginUtils.Rotation4D;
import pluginUtils.Vector2D;
import pluginUtils.Vector4D;




public class GeometricDrawer extends ImagePlus implements PlugIn{
	{Locale.setDefault(Locale.US); }
	
	private ImageProcessor primeIP; 
	private int X=2000,Y=2000; // image size
	
	
	private double xShift=0; 
	private double zShift=0; 
	private PrintStream outx; 
	

	private Random generator=new Random(); // One always needs some randomness
	
	// For the scaling of the image
	private double x0=0,x1=1,y0=0,y1=1;
	private double acoef,ccoef,vcoef,wcoef; 
	
	private static boolean voisin(int i,int j){
		int diff=0; 
		while(i+j!=0){
			if(i%2!=j%2) diff++;
			i=i/2;
			j=j/2; 
		}
		return diff==1; 
		
	}
	
	private String[] palette={"Yellow","Red","Blue","Green","White","NavyBlue","Turquoise","Orange"};
	private Color[] palette1={Color.YELLOW,Color.RED,Color.BLUE,Color.GREEN,Color.MAGENTA,Color.ORANGE};
	public void setCoefs(){
		acoef=X/(x1-x0); 
		vcoef=Y/(y1-y0); 
		ccoef=-acoef*x0; 
		wcoef=-vcoef*y0; 
	}
	 
	
	
	public void setBounds(double xl,double xu,double yl,double yu){
		x0=xl; 
		x1=xu;
		y0=yl;
		y1=yu; 
	}
	
	
	private void drawPoint(Point2D c){
		double xCenter=c.getX(); 
		double yCenter=c.getY(); 
		int intX=(int)(xCenter*acoef+ccoef);
		int intY=(int)(yCenter*vcoef+wcoef);
		primeIP.fillOval(intX-10,intY-10,20,20);
	}
	
	
	
	
	
	private void drawLine(double xd,double yd,double xf,double yf){
		int XD=(int)(xd*acoef+ccoef); 
		int YD=(int)(yd*vcoef+wcoef); 
		int XF=(int)(xf*acoef+ccoef); 
		int YF=(int)(yf*vcoef+wcoef);
		primeIP.drawLine(XD,YD,XF,YF); 
	}
	
	private void drawLine(Vector2D x1,Vector2D x2){
		int XD=(int)(x1.getX()*acoef+ccoef); 
		int YD=(int)(x1.getY()*vcoef+wcoef); 
		int XF=(int)(x2.getX()*acoef+ccoef); 
		int YF=(int)(x2.getY()*vcoef+wcoef);
		primeIP.drawLine(XD,YD,XF,YF); 
	}
		
	private static double dist=1.2; 
	private static double far(double u,double v){return (u*dist)/(dist-v);} 
	
	
	public void run(String arg) {
		primeIP = new ColorProcessor(X,Y);
		
		
		double limit=3; 
		
		setBounds(-limit,limit,-limit,limit); 
		setCoefs(); 
		
		
		
		
		
		
		Polygon background=new Polygon(new int[]{0,0,X,Y},new int[]{0,X,Y,0},4);
		primeIP.setColor(Color.WHITE);
		
		primeIP.fillPolygon(background);
		
		
		primeIP.setFont(new Font(null,Font.ITALIC,60));
		primeIP.setColor(Color.BLACK);
		primeIP.setLineWidth(1); 
	
		setProcessor("Verifying", primeIP);
		
		//drawLine(x0,0,x1,0);
		//drawLine(0,y0,0,y1);

		try{
		//	outx=new PrintStream("/tmp/zoo.txt");	
		outx=new PrintStream("C:\\Documents and Settings\\Francesco\\Bureau\\zono.txt");
		Polytope gege=Polytope.make120cell(); 
		double phi=(1.0+Math.sqrt(5))/2; 
		
		Matrix4D multy=Matrix4D.makeId(); 
		
		/*
		for(int i=0;i<6;i++){
			double ducon=0; 
			if(i==4) ducon=phi; else ducon=0;
			multy=Matrix4D.mul(multy,new Rotation4D(i,Math.atan2(1,ducon))); 
		}
		*/
		
		System.out.println(multy); 
		ArrayList<Vector4D> sommets=gege.getVertices(); 
		for(Vector4D u:sommets){
			ArrayList<Vector4D> vois=u.getVoisins(); 
			for(Vector4D v:vois){
				Vector4D newU=multy.transfo(u); 
				Vector4D newV=multy.transfo(v);
				int a=2; 
				int b=1; 
				int c=0; 
				/*
				if((u.get(0)!=v.get(0))||
						(u.get(1)!=v.get(1))||
						(u.get(2)!=v.get(2)))
				{
				String s1="cylinder{<"+u.get(0)+","+u.get(1)+","+u.get(2)+">,<"+v.get(0)+","+v.get(1)+","+v.get(2)+">,rados texture{T0} finish{F0}}"; 
				outx.println(s1);
				}
				
				
				if((u.get(0)!=v.get(0))||
						(u.get(1)!=v.get(1))||
						(u.get(3)!=v.get(3))){
				String s2="cylinder{<"+u.get(0)+","+u.get(1)+","+u.get(3)+">,<"+v.get(0)+","+v.get(1)+","+v.get(3)+">,rados texture{T0} finish{F0}}"; 
				outx.println(s2);
				}
				*/
				
				if(
						(Math.abs(newU.get(a)-newV.get(a))>1e-8)
					||
					(Math.abs(newU.get(b)-newV.get(b))>1e-8)
					||
					(Math.abs(newU.get(c)-newV.get(c))>1e-8)
					)
						
				{
				String s3="cylinder{<"+newU.get(a)+","+newU.get(b)+","+newU.get(c)+">,<"+newV.get(a)+","+newV.get(b)+","+newV.get(c)+">,rados texture{T0} finish{F0}}"; 
				outx.println(s3);
				}
				
				/*
				if((u.get(1)!=v.get(1))||
						(u.get(2)!=v.get(2))||
						(u.get(3)!=v.get(3)))
				{
				String s4="cylinder{<"+u.get(1)+","+u.get(2)+","+u.get(3)+">,<"+v.get(1)+","+v.get(2)+","+v.get(3)+">,rados texture{T0} finish{F0}}"; 
				outx.println(s4);
				}
				*/
				
					//primeIP.setColor(new Color(0.5f+0.5f*generator.nextFloat()/2,0.5f+0.5f*generator.nextFloat()/2,0.5f+0.5f*generator.nextFloat()));
					drawLine(newU.get(a),newV.get(a),newU.get(b),newV.get(b));
				}
			}
		
			
		outx.println("");	
		}
		catch(Exception e){System.out.println(e);}
		show();
		}
	}	

	